package uk.ac.ebi.das.uniprot.image.util;

import org.apache.log4j.Logger;
import org.biodas.jdas.client.StyleSheetClient;
import org.biodas.jdas.exceptions.DASClientException;
import org.biodas.jdas.schema.stylesheet.DASSTYLE;
import org.biodas.jdas.schema.stylesheet.TYPE;
import uk.ac.ebi.das.uniprot.image.controller.FactoryInterface;
import uk.ac.ebi.das.uniprot.image.exception.ImageException;

import java.util.List;

/**
 * Created by IntelliJ IDEA.
 * User: ljgarcia
 * Date: 12-Apr-2011
 * Time: 09:56:13
 * To change this template use File | Settings | File Templates.
 */
public class StyleSheetHelper {
    private static Logger logger = Logger.getLogger(StyleSheetHelper.class);
    private static List<TYPE> styles = null;

    /**
     * Initializes the UniProt StyleSheet retrieval from the default URL.
     * @param factory factory Jdas factory (so jmock can be used)
     * @throws uk.ac.ebi.das.uniprot.image.exception.ImageException
     * @throws javax.xml.bind.JAXBException
     * @throws java.net.MalformedURLException
     */
    private static void initStyleSheetHelper (FactoryInterface factory) throws ImageException, DASClientException {
        String serverURL = RetrievalHelper.getDasReferenceURL();
        StyleSheetClient ssClient = factory.getStyleSheetClient();
        DASSTYLE style = null;
        try {
            style = ssClient.fetchData(serverURL);
        } catch (DASClientException e) {
            logger.error("The UniProt StyleSheet response cannot be parsed by JAXB (" + e.getClass().getCanonicalName() + "): " + e.getMessage());
            e.printStackTrace();
            throw e;
        }
        styles = style.getSTYLESHEET().getCATEGORY().get(0).getTYPE();
    }

    /**
     * Return the list of available styles.
     * @return
     */
    private static List<TYPE> getStyles() {
        return styles;
    }

    /**
     * Retrieves the associated fore or back colour for the cvId or type id.
     * @param factory factory Jdas factory (so jmock can be used)
     * @param byCvId If true retrieval is by cvId, otherwise by type id.
     * @param fore If true the fore colour is retrieve, otherwise the back colour.
     * @param cvIdOrType CvId or type id.
     * @return
     */
    private static String getColor(FactoryInterface factory, boolean byCvId, boolean fore, String cvIdOrType) {
        try {
            if (getStyles() == null) {
                initStyleSheetHelper(factory);
            }
            for (TYPE style:getStyles()) {
                if (style.getId().equals(cvIdOrType)) {
                    if (fore) {
                        return style.getGLYPH().get(0).getBOX().getFGCOLOR();
                    } else {
                        return style.getGLYPH().get(0).getBOX().getBGCOLOR();
                    }
                }
            }
            if (byCvId) {
                return FeatureTypeConfigHelper.fetchByCvId(cvIdOrType, null).getColor();
            } else {
                return FeatureTypeConfig.valueOf(cvIdOrType).getColor();
            }
        } catch (Exception e) {
            //e.printStackTrace();
            logger.info("It is not possible to retrieve the color from the Stylesheet for " + cvIdOrType + " thus the default color will be used");
            return FeatureTypeConfig.UNKNOWN.getColor();
        }
    }

    /**
     * Retrieves the associated BOX style fore colour by cvId.
     * @param factory factory Jdas factory (so jmock can be used)
     * @param cvId
     * @return
     */
    public static String getForeColorByCvId(FactoryInterface factory, String cvId) {
        return getColor(factory, true, true, cvId);
    }

    /**
     * Retrieves the associated BOX style fore colour by type (name).
     * @param factory factory Jdas factory (so jmock can be used)
     * @param type
     * @return
     */
    public static String getForeColorByType(FactoryInterface factory, String type) {
        return getColor(factory, false, true, type);
    }

    /**
     * Retrieves the associated BOX style back colour by cvId.
     * @param factory factory Jdas factory (so jmock can be used)
     * @param cvId
     * @return
     */
    public static String getBackColorByCvId(FactoryInterface factory, String cvId) {
        return getColor(factory, true, false, cvId);
    }

    /**
     * Retrieves the associated BOX style back colour by type (name).
     * @param factory factory Jdas factory (so jmock can be used)
     * @param type
     * @return
     */
    public static String getBackColorByType(FactoryInterface factory, String type)  {
        return getColor(factory, false, false, type);
    }
}
